package icraf.carbon.gui;

import icraf.carbon.core.Project;
import icraf.carbon.core.Zone.DataType;
import icraf.carbon.core.ZoneList;

import java.awt.BorderLayout;
import java.awt.Component;
import java.awt.event.MouseListener;

import javax.swing.JPanel;
import javax.swing.JTabbedPane;
import javax.swing.event.ChangeListener;
import javax.swing.event.TableModelListener;

public class LCMatrixTabPanel extends JPanel {
	private static final long serialVersionUID = 1122919881488352700L;
	private boolean isDiagonalColor = true;
	private Project project;
	private MouseListener rowMouseListener;
	private TableModelListener tableModelListener;
	private JTabbedPane tabPanel;
	private Component topComponent;
	private String unitDef;
	private boolean isUnitSelectable;
	private String unitArea;
	private boolean editable;
	private boolean isMenuDetail;
	private String menuDetailTitle;

	public LCMatrixTabPanel() {
		tabPanel = new JTabbedPane();
		tabPanel.setTabLayoutPolicy(JTabbedPane.SCROLL_TAB_LAYOUT);
		this.setLayout(new BorderLayout());
		this.add(tabPanel);
		
	}
	
	public void setTopComponent(Component c) {
		if(topComponent != null)
			this.remove(topComponent);
		this.add(c, BorderLayout.NORTH);
		topComponent = c;
	}

	public void fireTableDataChanged() {
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			MatrixPanel c = (MatrixPanel) tabPanel.getComponentAt(i);
			c.getMatrixTableModel().fireTableDataChanged();
		}
	}

	public Project getProject() {
		return project;
	}

	public MatrixPanel getSelectedPanel() {
		return (MatrixPanel) tabPanel.getSelectedComponent();
	}
	
	public int getSelectedPanelIndex() {
		return tabPanel.getSelectedIndex();
	}

	public JTabbedPane getTabPanel() {
		return tabPanel;
	}
	
	public void addZoneTabListener(ChangeListener l) {
		tabPanel.addChangeListener(l);
	}
	
	public void selectZoneTab(int i) {
		if(i < tabPanel.getTabCount())
			tabPanel.setSelectedIndex(i);
	}


	/**
	 * this define whether the scale is using zone area or total area
	 * @param isZoneAreaScale
	 */
	public void setZoneAreaScale(boolean isZoneAreaScale) {
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			lcPanel.setZoneAreaScale(isZoneAreaScale);
		}
	}
	
	public void setSelectUnitArea(boolean b) {
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			lcPanel.setSelectUnitArea(b);
		}
	}
	
	public void setAreaScale(boolean isAreaScale) {
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			((LCTableModel) lcPanel.getMatrixTableModel()).setAreaScale(isAreaScale, lcPanel.isZoneAreaScale());
		}
	}

	public void setCornerSetting(String unitDef, String unitArea,
			boolean isUnitSelectable) {
		this.unitDef = unitDef;
		this.unitArea = unitArea;
		this.isUnitSelectable = isUnitSelectable;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			MatrixPanel c = (MatrixPanel) tabPanel.getComponentAt(i);
			c.setUnit(unitDef, unitArea);
			c.setUnitSelectable(isUnitSelectable);
		}
	}

	public void setDataType(DataType t, Object attributes) {
		ZoneList zs = project.getZoneList();
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			tabPanel.setTitleAt(i, zs.get(i).getLabel());
			MatrixPanel c = (MatrixPanel) tabPanel.getComponentAt(i);
			((LCTableModel) c.getMatrixTableModel()).setProject(project, t,
					attributes);
			((LCTableModel) c.getMatrixTableModel()).setZoneIndex(i);

		}
	}

	public void setDiagonalColor(boolean isDiagonalColor) {
		this.isDiagonalColor = isDiagonalColor;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			MatrixPanel c = (MatrixPanel) tabPanel.getComponentAt(i);
			c.setDiagonalColor(isDiagonalColor);
		}
	}
	
	public void setMenuDetail(boolean b, String title) {
		isMenuDetail = b;
		menuDetailTitle = title;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			MatrixPanel c = (MatrixPanel) tabPanel.getComponentAt(i);
			c.setMenuDetail(b, title);
		}
	}

	public void setEditable(boolean editable) {
		this.editable = editable;
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			((LCTableModel) lcPanel.getMatrixTableModel())
					.setEditable(editable);
		}
	}
	
	public void resetValue() {
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			((LCTableModel) lcPanel.getMatrixTableModel())
					.resetValue();
		}
	}

	public void setNegativeAllowed(boolean isNegativeAllowed) {
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			((LCTableModel) lcPanel.getMatrixTableModel())
					.setNegativeAllowed(isNegativeAllowed);
		}
	}

	public void setProject(Project project) {
		if (project == null)
			return;
		this.project = project;
		updateTabZone();
	}

	public void setRowHighlight(boolean b, RowHighlight rowHighlight) {
		MatrixPanel lcPanel;
		for (int i = 0; i < tabPanel.getTabCount(); i++) {
			lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
			lcPanel.setRowHighlight(b, rowHighlight);
		}
	}

	/**
	 * should be called on the initialization step -> not good
	 * 
	 * @param l
	 */
	public void setRowMouseListener(MouseListener l) {
		this.rowMouseListener = l;
	}

	public void setTableModelListener(TableModelListener l) {
		tableModelListener = l;
	}

	public void updateTabZone() {
		ZoneList zs = project.getZoneList();
		for (int i = 0; i < zs.getSize(); i++) {
			MatrixPanel lcPanel;
			if (i < tabPanel.getTabCount()) {
				lcPanel = (MatrixPanel) tabPanel.getComponentAt(i);
				tabPanel.setTitleAt(i, zs.get(i).getLabel());
			} else {
				lcPanel = new MatrixPanel(new LCTableModel(true), true, true,
						true, true, true);
				tabPanel.addTab(zs.get(i).getLabel(), lcPanel);

				if (rowMouseListener != null) {
					lcPanel.getRowHeader().addMouseListener(rowMouseListener);
				}

				if (tableModelListener != null) {
					lcPanel.getMatrixTableModel().addTableModelListener(
							tableModelListener);
				}
			}
			LCTableModel m = (LCTableModel) lcPanel.getMatrixTableModel();
			m.setProject(project);
			m.setZoneIndex(i);
			m.setEditable(editable);
			lcPanel.setTotalFields(true);
			lcPanel.setDiagonalColor(isDiagonalColor);
			lcPanel.updateHighlight();
			lcPanel.setUnit(unitDef, unitArea);
			lcPanel.setUnitSelectable(isUnitSelectable);
			lcPanel.setMenuDetail(isMenuDetail,	menuDetailTitle);
			
		}
		int n = tabPanel.getTabCount() - zs.getSize();
		for (int i = 0; i < n; i++) {
			tabPanel.remove(zs.getSize());
		}
	}

	public void setProject(Project project, DataType dataType,
			Object attributes) {
		setProject(project);
		setDataType(dataType, attributes);
	}
}
